The following is intended to describe how to write clients that utilize the Generic and Specific Assess Service by using JAX-WS and .NET. It is assumed that the reader is reasonably proficient in web-service technology. Two samples are provided; one for generating client stub classes for JAX-WS using wsimport and the other for generating client stub classes using .NET.
The wsimport tool reads the Assess WSDL file and generates artifacts such as the service endpoint interface (proxy object for calling operations on the web-service) and data objects that model the web-service data. The -d option specifies the target directory to store the generated client classes. The keep option ensures that the source files are kept along side the class files.
In the following example, the WSDL is the Assess Service of the example rulebase called RuleBaseWithSimpleRelationships.
wsimport -d D:/client_directory -keep http://localhost:8080/determinations-server/assess/soap/specific/10.2/RuleBaseWithSimpleRelationships?wsdl
The stub provides method calls that expose the available operations on the web-service (wsdl ports). In the case of the Assess Service, we have two available operations which are ListGoals and Assess.
The following example shows a simple client that invokes the ListGoals operation on the Assess Service.The request object for the Generic and Specific service is the same. This operation returns a ListGoal response object with the goal attributes for the rule base.
/**
* Simple web-service client that will test the access web-service. (10.2 determinations
* server)
*
* @author ramrajan
*
*/
public class ListGoalsClient {
static OdsAssessServiceGeneric102RuleBaseWithSimpleRelationships assessStub;
static OdsAssessServiceGeneric102RuleBaseWithSimpleRelationshipsType assessServiceStubType;
public static void main(String[] args) {
ListGoalsClient client = new ListGoalsClient();
// set up the client stub to call operations on the web-service
client.setUpProxyForAssessService();
// retrieve attribute goals from the rule-base using the assess service
client.retrieveHighLevelGoals();
}
public void setUpProxyForAssessService() {
assessStub = new OdsAssessServiceGeneric102RuleBaseWithSimpleRelationships();
// initialise the stub
assessServiceStubType = assessStub.getOdsAssessServiceGeneric102RuleBaseWithSimpleRelationshipsSOAP();
}
/**
* Retrieves high level goals from the assess service
*/
public void retrieveHighLevelGoals() {
// create a list goals request object
ListGoalsRequest listGoalsRequest = new ListGoalsRequest();
// invoke the List Goals operation on the assess service which returns a response object
ListGoalsResponse listGoalsResponse = assessServiceStubType.listGoals(listGoalsRequest);
List<ListGoalsEntityType> listGoalsEntityType = listGoalsResponse.getEntity();
for (ListGoalsEntityType listGoal : listGoalsEntityType) {
System.out.println("Entity Id for goal ["+ listGoal.getEntityId() +"]");
List<ListGoalsAttributeType> attributesOfGoals = listGoal.getAttribute();
// scan through attributes
System.out.println("Listing attributes of goal ...");
for (ListGoalsAttributeType goalAttribute: attributesOfGoals) {
System.out.println(" ID [" + goalAttribute.getId() + "]");
System.out.println(" Text [" + goalAttribute.getText() + "]");
System.out.println(" Type [" + goalAttribute.getType().toString() + "]");
}
}
}
}
In the example above, assessStub.getOdsAssessServiceGeneric102RuleBaseWithSimpleRelationshipsSOAP() calls the getPort method which respectively returns a static stub which we can use to call operations on the Assess Service:
/**
*
* @return
* returns OdsAssessServiceSpecific102RuleBaseWithSimpleRelationshipsType
*/
@WebEndpoint(name = "odsAssessServiceSpecific102_RuleBaseWithSimpleRelationships_SOAP")
public OdsAssessServiceSpecific102RuleBaseWithSimpleRelationshipsType getOdsAssessServiceSpecific102RuleBaseWithSimpleRelationshipsSOAP() {
return super.getPort(new QName("http://oracle.com/determinations/server/10.2/RuleBaseWithSimpleRelationships/assess/types",
"odsAssessServiceSpecific102_RuleBaseWithSimpleRelationships_SOAP"), OdsAssessServiceSpecific102RuleBaseWithSimpleRelationshipsType.class);
}
In the example client, the assess request data object and other data objects which are consumed by the Assess operation have already been generated by the wsimport tool. Refer to the assess request elements (note:link here), the request has an optional configuration element and a mandatory global instance element. The example below has the following rule in it's rulebase:
* The teacher is happy if * Exists(the children, the child is happy)
Now, lets create a simple assess request to infer if the teacher is happy based on one of the child instances being happy. Please refer to the example code and the notes below.
package com.oracle.determinations.client;
import java.math.BigDecimal;
import java.util.GregorianCalendar;
import javax.xml.datatype.DatatypeConfigurationException;
import javax.xml.datatype.DatatypeFactory;
import javax.xml.datatype.XMLGregorianCalendar;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.AssessRequest;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.AssessResponse;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.AttributeTypeEnum;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.BooleanAttributeType;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.DateAttributeType;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.GlobalInstanceType;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.NumberAttributeType;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.OdsAssessServiceSpecific102RuleBaseWithSimpleRelationships;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.OdsAssessServiceSpecific102RuleBaseWithSimpleRelationshipsType;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.OutcomeStyleEnum;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.TheChildEntityListType;
import com.oracle.determinations.server._10_2.rulebasewithsimplerelationships.assess.types.TheChildInstanceType;
/**
* This client aims to test the Assess Web-Service layer. The main intention is to use a
* simple rule-base which has an global attribute and the the outcome is determined by
* the instances of entity-level attributes.
*
* <code>
* The teacher is happy if
* Exists(the children, the child is happy)
* </code>
*
* @author ramrajan
*
*/
public class AssessClient {
private static String CHILD_ENTITY_ID = "the_child";
private static String CHILD_ENTITY_LEVEL_ATTR = "child_is_happy";
static OdsAssessServiceSpecific102RuleBaseWithSimpleRelationships assessStub;
static OdsAssessServiceSpecific102RuleBaseWithSimpleRelationshipsType assessServiceStubType;
public static void main(String[] args) {
AssessClient client = new AssessClient();
client.setUpProxyForAssessService();
client.testEntityRelationship();
client.testDateAndCurrencyDataTypes();
}
public void setUpProxyForAssessService() {
assessStub = new OdsAssessServiceSpecific102RuleBaseWithSimpleRelationships();
assessServiceStubType = assessStub.getOdsAssessServiceSpecific102RuleBaseWithSimpleRelationshipsSOAP();
}
/**
* Create instances of entities with their attributes set.
*
* @return
*/
public void testEntityRelationship() {
System.out.println("Create Assess Request object.");
AssessRequest assessRequest = new AssessRequest();
// Everything is contained within a global instance.
GlobalInstanceType globalInstanceType = new GlobalInstanceType();
globalInstanceType.setTeacherHappy(new BooleanAttributeType());
globalInstanceType.getTeacherHappy().setOutcomeStyle(OutcomeStyleEnum.DECISION_REPORT);
globalInstanceType.setListTheChild(new TheChildEntityListType());
// Child instance - mark
TheChildInstanceType childInstance1 = new TheChildInstanceType();
childInstance1.setId("mark");
BooleanAttributeType markHappyAttribute = new BooleanAttributeType();
markHappyAttribute.setType(AttributeTypeEnum.BOOLEAN);
markHappyAttribute.setBooleanVal(true);
childInstance1.setChildIsHappy(markHappyAttribute);
// Create an entity instance for child
globalInstanceType.getListTheChild().getTheChild().add(childInstance1);
assessRequest.setGlobalInstance(globalInstanceType);
AssessResponse assessResponse = assessServiceStubType
.assess(assessRequest);
GlobalInstanceType globalInstanceResponse = assessResponse
.getGlobalInstance();
System.out
.println("Infered value for teacher being happy ["
+ globalInstanceResponse.getTeacherHappy()
.isBooleanVal() + "]");
}
/**
* Test currency and date attributes.
* @return
*/
public void testDateAndCurrencyDataTypes() {
AssessRequest assessRequest = new AssessRequest();
// Everything is contained within a global instance.
GlobalInstanceType globalInstanceType = new GlobalInstanceType();
globalInstanceType.setPersonCompensation(new BooleanAttributeType());
globalInstanceType.getPersonCompensation().setOutcomeStyle(OutcomeStyleEnum.DECISION_REPORT);
globalInstanceType.setPersonIncome(new NumberAttributeType());
globalInstanceType.getPersonIncome().setNumberVal(new BigDecimal("25000.00"));
GregorianCalendar calendar = new GregorianCalendar();
calendar.set(1999, 01, 01);
XMLGregorianCalendar xgcal = null;
try {
xgcal = DatatypeFactory.newInstance().newXMLGregorianCalendar(calendar);
} catch (DatatypeConfigurationException dce) {
dce.printStackTrace();
}
globalInstanceType.setPersonDob(new DateAttributeType());
globalInstanceType.getPersonDob().setDateVal(xgcal);
assessRequest.setGlobalInstance(globalInstanceType);
AssessResponse assessResponse = assessServiceStubType
.assess(assessRequest);
System.out.println("Is person eligible for compensation ["
+ assessResponse.getGlobalInstance().getPersonCompensation()
.isBooleanVal() + "]");
}
}
It's just a simple matter of point and click to generate a web-service assess client using Visual Studio. To generate the classes, go to Project -> Add Service Reference, paste the WSDL url in the Address field and click on Go. Then when you have located the right service, type in a namespace and click on Ok.
namespace WSAssessClientSpecific10_2
{
class AssessClient
{
static odsAssessServiceSpecific102_RuleBaseWithSimpleRelationships_typeClient proxy;
static void Main(string[] args)
{
Console.WriteLine("Assess client specific for 10.2");
AssessClient client = new AssessClient();
proxy = new odsAssessServiceSpecific102_RuleBaseWithSimpleRelationships_typeClient();
client.getHighLevelGoals();
client.identifyTeacherIsHappy();
client.identifyPersonEligibleForCompensation();
}
public void getHighLevelGoals()
{
listgoalsrequest request = new listgoalsrequest();
ListGoalsEntityType[] goalsList = proxy.ListGoals(request);
foreach (ListGoalsEntityType goalEntity in goalsList)
{
ListGoalsAttributeType[] attributeList = goalEntity.attribute;
foreach (ListGoalsAttributeType attribute in attributeList)
{
Console.WriteLine("ID :[" + attribute.id + "] Text: [" + attribute.text + "]");
}
}
}
public void identifyTeacherIsHappy()
{
AssessRequest assessRequest = new AssessRequest();
GlobalInstanceType globalInstanceType = new GlobalInstanceType();
globalInstanceType.teacher_happy = new booleanAttributeType();
globalInstanceType.teacher_happy.outcomestyle = OutcomeStyleEnum.decisionreport;
globalInstanceType.teacher_happy.outcomestyleSpecified = true;
globalInstanceType.listthe_child = new the_childEntityListType();
globalInstanceType.listthe_child.the_child = new the_childInstanceType[1];
the_childInstanceType childInstance = new the_childInstanceType();
childInstance.id = "mark";
booleanAttributeType booleanAttribute = new booleanAttributeType();
booleanAttribute.Item = true;
childInstance.child_is_happy = booleanAttribute;
globalInstanceType.listthe_child.the_child.SetValue(childInstance, 0);
assessRequest.globalinstance = globalInstanceType;
AssessResponse assessResponse = proxy.Assess(assessRequest);
Console.WriteLine("Is the teacher happy [" + assessResponse.globalinstance.teacher_happy.Item + "]");
}
public void identifyPersonEligibleForCompensation()
{
AssessRequest assessRequest = new AssessRequest();
GlobalInstanceType globalInstanceType = new GlobalInstanceType();
globalInstanceType.person_compensation = new booleanAttributeType();
globalInstanceType.person_compensation.outcomestyle = OutcomeStyleEnum.decisionreport;
globalInstanceType.person_compensation.outcomestyleSpecified = true;
globalInstanceType.person_income = new numberAttributeType();
globalInstanceType.person_income.type = AttributeTypeEnum.currency;
globalInstanceType.person_income.Item = new Decimal(1500000.00);
assessRequest.globalinstance = globalInstanceType;
AssessResponse assessResponse = proxy.Assess(assessRequest);
Console.WriteLine("Is the person eligible for compensation [ " + assessResponse.globalinstance.person_compensation.Item + "]");
}
}
}